import React, { useContext, useState, useEffect, useRef } from 'react';
import { Input, Form, Select } from 'antd';
// @ts-ignore
import { getMessage } from '@inbiz/react';
import MultilingualInput from '@inbiz/basic/MultilingualInput';
import { ConditionEditableContext } from './Expression';
import { ExchangeVariableEditableContext } from './ExchangeVariable';
import { OpButtonEditableContext } from './ButtonTable';

// 可修改表格组件-行
const EditableRow = (props: any) => <tr {...props} />;

interface EditableCellProps {
  title: React.ReactNode;
  editable: boolean;
  children: React.ReactNode;
  dataIndex: string;
  record: any;
  variateId: string;
  pcControl: any[];
  h5Control: any[];
  required: boolean;
  setNowKey: (b: string) => void;
  handleSave: (record: any) => void;
  variateList?: any[];
  parentList?: any[];
  childList?: any[];
}

// 可修改表格组件-列（单元格）
const EditableCell = ({
  title,
  editable,
  children,
  dataIndex,
  record,
  required,
  variateId,
  pcControl,
  h5Control,
  setNowKey,
  handleSave,
  variateList,
  parentList,
  childList,
  ...restProps
}: EditableCellProps) => {
  const [editing, $Editing] = useState(false);
  const inputRef = useRef(null);
  const form = useContext(record?.id?.startsWith('condition') ? ConditionEditableContext : record?.id?.startsWith('button') ? OpButtonEditableContext : ExchangeVariableEditableContext);

  useEffect(() => {
    if (editing && inputRef.current) {
      let dom: HTMLElement = inputRef.current;
      dom?.focus();
    }
  }, [editing]);

  const toggleEdit = () => {
    setNowKey(record.id);
    $Editing(true);
    // @ts-ignore
    form.setFieldsValue({ [dataIndex]: record[dataIndex] });
  };

  const save = async () => {
    try {
      const values = await form.validateFields();
      let row: any = { ...record };
      let recordD = { ...row, ...values };
      handleSave(recordD);
    } catch (err) { }
    $Editing(false);
  };

  let childNode = children;

  if (editable) {
    const placeMessage = getMessage('ProcessManagement.placeMessage');
    const setVariate_message = getMessage('ProcessManagement.setVariate_message');
    const setVariate_name_message = getMessage('ProcessManagement.setVariate_name_message');
    childNode =
      editing && variateId === record.id ? (
        <Form.Item
          style={{ margin: 0 }}
          name={dataIndex}
          rules={
            required
              ? dataIndex === 'varName'
                ? [
                  {
                    required: true,
                    message: setVariate_name_message,
                  },
                  {
                    pattern: /^[a-zA-Z][a-zA-Z\d]*$/,
                    message: setVariate_message,
                  },
                ]
                : [
                  {
                    required: true,
                    message: setVariate_name_message,
                  },
                ]
              : []
          }
        >
          {['leftBracket'].includes(dataIndex) ? (
            <Select ref={inputRef} onBlur={save} allowClear placeholder={placeMessage} getPopupContainer={() => document.body}>
              <Select.Option value={''}>{''}</Select.Option>
              <Select.Option value={'('}>{'('}</Select.Option>
            </Select>
          ) : ['varName'].includes(dataIndex) ? (
            <Select ref={inputRef} onBlur={save} allowClear placeholder={placeMessage} getPopupContainer={() => document.body}>
              {variateList?.map((item: any) => {
                return <Select.Option value={item.varName}>{item.varName}</Select.Option>;
              })}
            </Select>
          ) : ['symbolicLogic'].includes(dataIndex) ? (
            <Select ref={inputRef} onBlur={save} allowClear placeholder={placeMessage} getPopupContainer={() => document.body}>
              <Select.Option value={'=='}>{'=='}</Select.Option>
              <Select.Option value={'>'}>{'>'}</Select.Option>
              <Select.Option value={'<'}>{'<'}</Select.Option>
              <Select.Option value={'>='}>{'>='}</Select.Option>
              <Select.Option value={'<='}>{'<='}</Select.Option>
              <Select.Option value={'!='}>{'!='}</Select.Option>
            </Select>
          ) : ['compareValue', 'type'].includes(dataIndex) ? (
            <Input ref={inputRef} onPressEnter={save} onBlur={save} placeholder={placeMessage} />
          ) : ['rightBracket'].includes(dataIndex) ? (
            <Select ref={inputRef} onBlur={save} allowClear placeholder={placeMessage} getPopupContainer={() => document.body}>
              <Select.Option value={''}>{''}</Select.Option>
              <Select.Option value={')'}>{')'}</Select.Option>
            </Select>
          ) : ['logic'].includes(dataIndex) ? (
            <Select ref={inputRef} onBlur={save} allowClear placeholder={placeMessage} getPopupContainer={() => document.body}>
              <Select.Option value={''}>{''}</Select.Option>
              <Select.Option value={'||'}>{'||'}</Select.Option>
              <Select.Option value={'&&'}>{'&&'}</Select.Option>
            </Select>
          ) : ['pin', 'sout'].includes(dataIndex) ? (
            <Select ref={inputRef} onBlur={save} allowClear placeholder={placeMessage} getPopupContainer={() => document.body}>
              {parentList?.map((item: any) => {
                return <Select.Option value={item.varName}>{item.varName}</Select.Option>;
              })}
            </Select>
          ) : ['pout'].includes(dataIndex) ? (
            <Select ref={inputRef} onBlur={save} allowClear placeholder={placeMessage} getPopupContainer={() => document.body}>
              {childList?.map((item: any) => {
                return <Select.Option value={item.varName}>{item.varName}</Select.Option>;
              })}
            </Select>
          ) : ['name'].includes(dataIndex) ? (
            <MultilingualInput onBlur={save} />
          ) : null}
        </Form.Item>
      ) : (
        <div
          className="editable-cell-value-wrap"
          id={`cell-${dataIndex}-${record.id}`}
          onClick={toggleEdit}
          // @ts-ignore
          title={children?.[1] || ''}
        >
          {children}
        </div>
      );
  }

  return <td {...restProps}>{childNode}</td>;
};

export { EditableRow, EditableCell };
